// PongGame.h
//
// (Free support code)
//
// You may need to modify this file, especially to
// add new fields to the PongGame class as needed.
//


// A class representing a colored material
// (you probably don't need to edit this)

	#include "Ball.h"


class MaterialInfo {
private:
  float specular[4];
  float ambient [4];
  float diffuse [4];
  float shininess;

public:
  MaterialInfo (float r, float g, float b, float a) {
    specular[0] = ambient[0] = diffuse[0] = r;
    specular[1] = ambient[1] = diffuse[1] = g;
    specular[2] = ambient[2] = diffuse[2] = b;
    specular[3] = ambient[3] = diffuse[3] = a;
    shininess = 100.0;
  }

  MaterialInfo() { }

  float *getSpecular() { return specular; }
  float *getDiffuse() { return diffuse; }
  float *getAmbient() { return ambient; }
  float getShininess() { return shininess; }

};


// A class representing our program
// You will likely need to modify this (to add fields to the class):
class PongGame {


 public:
  // PUBLIC METHODS:

  PongGame(); // Constructor
  virtual ~PongGame(); // Destructor
  void initializePongGame();                        // Data structure initialization method (called by main)
  void keyDown(unsigned char key, int x, int y);	// Key pressed GLUT callback
  void mouseClick(int button,int state, int x, int y);
  void mouseDrag(int x,int y);
  void idle();										// idle GLUT callback

  void redraw();									// Redraw GLUT callback
  void reshape (int w, int h);						// Window reshape GLUT callback
  void initGL();									// OpenGL initialization (called by main)
	
 private:
  // PRIVATE METHODS:

  // Draws your robot (called by redraw())
  void drawPongGame();

  // You can use this to change the current rendering material
  void setGLMaterial(MaterialInfo m);
  void setInnerGLMaterial(MaterialInfo m);
  
  // Turns on the lights
  void lights(void);
  
  // Draws an x,y,z coordinate frame (call this to help you
  // find your current origin)
  void draw_axes();

  // Draws an axis representation along the z-axis:
  void draw_axis(double length);

  //tells you if pos is inside a cup or not.
  bool inCup(vector<double> pos);
  bool onCup(vector<double> pos);

  void drawMesh();
  void loadModel(const char* filename);

  void switch_cups();

  GLuint CUP_DL;
  GLuint ENV_DL;
  GLuint TABLE_DL;
  GLuint table_tex;
  GLuint floor_tex;
  GLuint sawin_tex;
  GLuint akers_tex;

  Mesh m;

  GLUquadric *quadric;
  double ballpos[3];

  //Various measurements
  double tablex;
  double tablez;
  double cup_h;
  double cup_br;
  double cup_tr;
  double ball_r;

  std::vector<bool> cups;
  std::vector<bool> player_cups;
  std::vector<vector<double>> cup_pos;

  
  double anim[10]; //0 = horiz cam angle
  int status[5];  // Game status

  Ball ball;

  int phase;

  //idle values
  double last_idle;

  // used during throw
  boolean lHold;
  int startX;
  int startY;
  int bounces;
  double lastCupHit;

  double tStart; //when throw started
  double originalStart; //when the first throw started (not bounces)

  double power;
  double upAng;
  double hAng;
  //end

  //camera values
  boolean rHold;
  int lLastX;
  int lLastY;
  double viewX;
  double viewY;

  //Screen dimensions
  int sx, sy;


  //Text stuff
  double msgTime;

  string miss[10];
  string hit[10];
  string win[2];
  string loss[2];

  string curMsg;

};

// GLOBAL variables (constants):

// Some materials you can use in your program
MaterialInfo MAT_WHITE (1.0,1.0,1.0,1.0);
MaterialInfo MAT_GRAY  (0.5,0.5,0.5,1.0);
MaterialInfo MAT_BLUE  (0.1,0.1,0.6,1.0);
MaterialInfo MAT_GREEN (0.0,1.0,0.0,1.0);
MaterialInfo MAT_RED   (0.6,0.1,0.1,1.0);
MaterialInfo MAT_YELLOW(0.5,0.5,0.0,1.0);
MaterialInfo MAT_WALL(0.3,0.4,0.5,1.0);

MaterialInfo MAT_WHITETRANS (1.0,1.0,1.0,.3);
MaterialInfo MAT_BEER (0.6,0.4,0.1,.6);
MaterialInfo MAT_REDTRANS (1.0,0.0,0.0,.3);
MaterialInfo MAT_GREENTRANS (0.0,1.0,0.0,.6);

//static const double PI = 3.141593;
//const double DEG_TO_RAD = PI / 180.;
static PongGame *instance = NULL; // Hack to make GLUT play nicely with C++.
